﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Utilities;

namespace BusinessLogicLayer
{
    public static class TrangThaiNV
    {
        public static readonly string OnSite = "On-Site";
        public static readonly string LamViec = "Làm việc";
        public static readonly string RanhRoi = "Rảnh rỗi";
        public static readonly string NghiViec = "Nghỉ việc";
    }

    public class NhanVienManager
    {
        /// <summary>
        /// Lấy toàn bộ danh sách nhân viên
        /// </summary>
        /// <returns></returns>
        public ActionResultAsList<NhanVien> LayDS()
        {
            var ar = new ActionResultAsList<NhanVien>();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    ar.ObjectList = db.NhanViens.Include("ChucVu1").Include("NhanVien2").ToList();
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ar.AddException(ex);
            }
            return ar;
        }

        /// <summary>
        /// Lấy danh sách nhân viên hiện hành - không phải sinh viên thực tập và không nghỉ việc
        /// </summary>
        /// <returns></returns>
        public ActionResultAsList<NhanVien> LayDSHienHanh()
        {
            var ar = new ActionResultAsList<NhanVien>();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    ar.ObjectList = db.NhanViens.Include("ChucVu1").Include("NhanVien2").Where(n => n.TrangThai != TrangThaiNV.NghiViec && n.ChucVu != "SVTT").ToList();
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ar.AddException(ex);
            }
            return ar;
        }

        /// <summary>
        /// Lấy nhân viên cuối cùng
        /// </summary>
        /// <returns></returns>
        public ActionResultAsList<NhanVien> LayNVCuoi()
        {
            var ar = new ActionResultAsList<NhanVien>();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    List<NhanVien> l = db.NhanViens.Include("ChucVu1").Include("NhanVien2").ToList();
                    if (l.Count > 0)
                        ar.ObjectList.Add(l.Last());
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ar.AddException(ex);
            }
            return ar;
        }

        /// <summary>
        /// Thêm nhân viên
        /// </summary>
        /// <param name="nv"></param>
        /// <returns></returns>
        public ActionResult Them(NhanVien nv)
        {
            ActionResult ac = new ActionResult();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    List<NhanVien> list = db.NhanViens.ToList();
                    if (list.Exists(n => n.MaNhanVien == nv.MaNhanVien))
                    {
                        ac.AddException(new Exception("Mã nhân viên đã tồn tại: " + nv.MaNhanVien));
                        return ac;
                    }
                    db.NhanViens.Add(nv);
                    db.SaveChanges();
                    nv = db.NhanViens.Include("ChucVu1").Include("NhanVien2").Single(n => n.MaNhanVien == nv.MaNhanVien);
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ac.AddException(ex);
            }
            return ac;
        }

        /// <summary>
        /// Cập nhật danh sách kỹ năng cho nhân viên theo mã
        /// </summary>
        /// <param name="maNV"></param>
        /// <param name="dsKN"></param>
        /// <returns></returns>
        public ActionResult CapNhatDSKyNang(string maNV, List<string> dsKN)
        {
            ActionResult ac = new ActionResult();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    NhanVien nv = db.NhanViens.Include("KyNangs").Single(n => n.MaNhanVien == maNV);
                    nv.KyNangs.Clear();
                    foreach (string ma in dsKN)
                    {
                        KyNang kn = db.KyNangs.Single(k => k.MaKyNang == ma);
                        nv.KyNangs.Add(kn);
                    }
                    db.SaveChanges();
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ac.AddException(ex);
            }
            return ac;
        }

        /// <summary>
        /// Cập nhật thông tin nhân viên
        /// </summary>
        /// <param name="nv"></param>
        /// <returns></returns>
        public ActionResult CapNhat(ref NhanVien nv)
        {
            ActionResult ac = new ActionResult();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    string maNV = nv.MaNhanVien;
                    NhanVien nv1 = db.NhanViens.Single(n => n.MaNhanVien == maNV);
                    nv1.HoNhanVien = nv.HoNhanVien;
                    nv1.TenNhanVien = nv.TenNhanVien;
                    nv1.CMND = nv.CMND;
                    nv1.GioiTinh = nv.GioiTinh;
                    nv1.DiaChi = nv.DiaChi;
                    nv1.Email = nv.Email;
                    nv1.NgaySinh = nv.NgaySinh;
                    nv1.SoDienThoai = nv.SoDienThoai;
                    nv1.ChucVu = nv.ChucVu;
                    nv1.ChuKyHopDong = nv.ChuKyHopDong;
                    nv1.NgayNhan = nv.NgayNhan;
                    nv1.NgayBDLam = nv.NgayBDLam;
                    nv1.NgayKyLaiHD = nv.NgayKyLaiHD;
                    nv1.NhanVienQuanLy = nv.NhanVienQuanLy;
                    nv1.TrangThai = nv.TrangThai;
                    db.SaveChanges();
                    nv = db.NhanViens.Include("ChucVu1").Include("NhanVien2").Single(n => n.MaNhanVien == maNV);
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ac.AddException(ex);
            }
            return ac;
        }

        /// <summary>
        /// Lấy thông tin chi tiết nhân viên theo mã
        /// </summary>
        /// <param name="maNV"></param>
        /// <returns></returns>
        public ActionResultAsList<NhanVien> LayTTCTTheoMa(string maNV)
        {
            var ar = new ActionResultAsList<NhanVien>();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    NhanVien nv = db.NhanViens.Include("ChucVu1").Include("DKTangCas").Include("DuAnQuaKhus").Include("HoSoUngViens").
                        Include("NghiPheps").Include("NhanVien1").Include("NhanVien2").Include("DuAns").Include("OnSites").Include("KyNangs").Single(n => n.MaNhanVien == maNV);
                    ar.ObjectList.Add(nv);
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ar.AddException(ex);
            }
            return ar;
        }

        /// <summary>
        /// Xóa nhân viên theo mã
        /// </summary>
        /// <param name="maNV"></param>
        /// <returns></returns>
        public ActionResult Xoa(string maNV)
        {
            var ac = new ActionResult();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    NhanVien nv = db.NhanViens.Include("DKTangCas").Include("DuAnQuaKhus").Include("HoSoUngViens").Include("NghiPheps").
                        Include("NhanVien1").Include("DuAns").Include("OnSites").Include("KyNangs").Single(n => n.MaNhanVien == maNV);

                    new DuAnQKManager().XoaBenNhanVien(maNV);

                    foreach (var hs in nv.HoSoUngViens)
                    {
                        hs.NhanVienPhongVan = null;
                    }

                    foreach (var n in nv.NhanVien1)
                    {
                        n.NhanVienQuanLy = null;
                    }

                    db.DKTangCas.RemoveRange(nv.DKTangCas);
                    db.NghiPheps.RemoveRange(nv.NghiPheps);
                    nv.DuAns.Clear();
                    nv.OnSites.Clear();
                    nv.KyNangs.Clear();
                    db.NhanViens.Remove(nv);
                    db.SaveChanges();
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ac.AddException(ex);
            }
            return ac;
        }

        /// <summary>
        /// Sa thải nhân viên theo mã
        /// </summary>
        /// <param name="maNV"></param>
        /// <returns></returns>
        public ActionResult SaThai(string maNV)
        {
            var ac = new ActionResult();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    NhanVien nv = db.NhanViens.Include("NhanVien1").Single(n => n.MaNhanVien == maNV);

                    foreach (var n in nv.NhanVien1)
                    {
                        n.NhanVienQuanLy = null;
                    }

                    nv.TrangThai = TrangThaiNV.NghiViec;

                    db.SaveChanges();
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ac.AddException(ex);
            }
            return ac;
        }

        /// <summary>
        /// Tìm kiếm nhân viên theo các tiêu chí
        /// </summary>
        /// <param name="ten"></param>
        /// <param name="sdt"></param>
        /// <param name="diaChi"></param>
        /// <param name="email"></param>
        /// <param name="tenKNNN"></param>
        /// <param name="tenKNCM"></param>
        /// <returns></returns>
        public ActionResultAsList<NhanVien> TimKiem(string ten, string sdt, string diaChi, string email, string tenKNNN, string tenKNCM)
        {
            var ar = new ActionResultAsList<NhanVien>();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    var list = db.NhanViens.Include("ChucVu1").Include("NhanVien2").Where(n => n.TenNhanVien.Contains(ten)
                        && n.SoDienThoai.Contains(sdt)
                        && n.DiaChi.Contains(diaChi)
                        && n.Email.Contains(email)
                        && (n.KyNangs.Any(k => k.LoaiKyNang == "Ngoại ngữ" && k.TenKyNang.Contains(tenKNNN)) || tenKNNN == "")
                        && (n.KyNangs.Any(k => k.LoaiKyNang == "Chuyên môn" && k.TenKyNang.Contains(tenKNCM)) || tenKNCM == ""));
                    ar.ObjectList = list.ToList();
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ar.AddException(ex);
            }
            return ar;
        }

        /// <summary>
        /// Lấy danh sách nhân viên theo trạng thái
        /// </summary>
        /// <param name="trangThai"></param>
        /// <returns></returns>
        public ActionResultAsList<NhanVien> LayDSTheoTT(string trangThai)
        {
            var ar = new ActionResultAsList<NhanVien>();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    var list = db.NhanViens.Include("ChucVu1").Include("NhanVien2").Where(n => n.TrangThai == trangThai);
                    ar.ObjectList = list.ToList();
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ar.AddException(ex);
            }
            return ar;
        }

        /// <summary>
        /// Lấy danh sách nhân viên theo chức vụ
        /// </summary>
        /// <param name="maCV"></param>
        /// <returns></returns>
        public ActionResultAsList<NhanVien> LayDSTheoCV(string maCV)
        {
            var ar = new ActionResultAsList<NhanVien>();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    var list = db.NhanViens.Include("ChucVu1").Include("NhanVien2").Where(n => n.ChucVu == maCV);
                    ar.ObjectList = list.ToList();
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ar.AddException(ex);
            }
            return ar;
        }
        
        /// <summary>
        /// Lấy danh sách nhân viên theo mã nhân viên quản lý
        /// </summary>
        /// <param name="ten"></param>
        /// <returns></returns>
        public ActionResultAsList<NhanVien> LayDSTheoNVQL(string ten)
        {
            var ar = new ActionResultAsList<NhanVien>();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    var list = db.NhanViens.Include("ChucVu1").Include("NhanVien2").Where(n => n.NhanVien2.TenNhanVien.Contains(ten));
                    ar.ObjectList = list.ToList();
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ar.AddException(ex);
            }
            return ar;
        }

        /// <summary>
        /// Lấy thông tin nhân viên để in
        /// </summary>
        /// <param name="maNV"></param>
        /// <returns></returns>
        public ActionResultAsList<NhanVien> LayTTDeInTheoMa(string maNV)
        {
            var ar = new ActionResultAsList<NhanVien>();
            try
            {
                using (var db = new QLNVDbContext())
                {
                    NhanVien nv = db.NhanViens.Include("ChucVu1").Include("NhanVien2").Include("DuAns").Include("KyNangs").Single(n => n.MaNhanVien == maNV);
                    ar.ObjectList.Add(nv);
                }
            }
            catch (Exception ex)
            {
                Logger.Write(ex);
                ar.AddException(ex);
            }
            return ar;
        }
    }
}
